//
// Created by yangw on 2018-3-6.
//

#include "MNQueue.h"

MNQueue::MNQueue(TSPlayerStatus *plays) {

    this->playstatus = plays;
    pthread_mutex_init(&mutexPacket, NULL);
    pthread_cond_init(&condPacket, NULL);
}

MNQueue::~MNQueue() {
    clearAvpacket();
}

int MNQueue::getAvpacket(AVPacket *packet) {
    if (playstatus!= nullptr){
        LOGCATE("-------->getAvpacket 12 %d",playstatus->exit);
    }else{
        LOGCATE("-------->v getAvpacket 12");
    }

    pthread_mutex_lock(&mutexPacket);
    if (playstatus!= nullptr){
        LOGCATE("--------nullptr>getAvpacket 12 %d",playstatus->exit);
    }else{
        LOGCATE("-------->pthread_mutex_lock getAvpacket 12");
    }

    while (playstatus != nullptr&&!playstatus->exit){
        if (queuePacket.size()>0){
            LOGCATE("-------->getAvpacket22 1");
            AVPacket  *avPacket=queuePacket.front();
            if (av_packet_ref(packet,avPacket)==0){
                queuePacket.pop();
            }
            LOGCATE("-------->getAvpacket222 1");
            av_packet_free(&avPacket);

            av_free(avPacket);
            avPacket= nullptr;
            break;
        }else{
            pthread_cond_wait(&condPacket,&mutexPacket);
        }
    }
    pthread_mutex_unlock(&mutexPacket);

    return 0;



}

int MNQueue::putAvpacket(AVPacket *packet) {

    pthread_mutex_lock(&mutexPacket);
    LOGCATE("putAvpacket");
    queuePacket.push(packet);
    pthread_cond_signal(&condPacket);
    pthread_mutex_unlock(&mutexPacket);

    return 0;

}

int MNQueue::getQueueSize() {
    int size = 0;
    pthread_mutex_lock(&mutexPacket);
    LOGCATE("getQueueSize");
    size = queuePacket.size();
    LOGCATE("getQueueSize %d",size);
    pthread_mutex_unlock(&mutexPacket);

    return size;
}


int MNQueue::push(AVPacket *packet) {

    pthread_mutex_lock(&mutexPacket);
    LOGCATE("push");
    queuePacket.push(packet);
    pthread_cond_signal(&condPacket);
    pthread_mutex_unlock(&mutexPacket);

    return 0;
}

int MNQueue::get(AVPacket *packet) {

    pthread_mutex_lock(&mutexPacket);

    while(true)
    {
        if(queuePacket.size() > 0)
        {
            AVPacket *avPacket =  queuePacket.front();
            if(av_packet_ref(packet, avPacket) == 0)
            {
                queuePacket.pop();
            }
            av_packet_free(&avPacket);
            av_free(avPacket);
            avPacket = NULL;
            break;
        } else{
            pthread_cond_wait(&condPacket, &mutexPacket);
        }
    }
    pthread_mutex_unlock(&mutexPacket);
    return 0;
}

int MNQueue::size() {
    int size = 0;
    pthread_mutex_lock(&mutexPacket);
    size = queuePacket.size();
    pthread_mutex_unlock(&mutexPacket);
    return size;
}

void MNQueue::clearAvpacket() {
    pthread_cond_signal(&condPacket);
    pthread_mutex_unlock(&mutexPacket);

    while (!queuePacket.empty())
    {
        AVPacket *packet = queuePacket.front();
        queuePacket.pop();
        av_packet_free(&packet);
        av_free(packet);
        packet = NULL;
    }
    pthread_mutex_unlock(&mutexPacket);

}
